using System;
using System.Collections.Generic;
using System.Text;
using System.ComponentModel;

namespace Mud.Common.Physical
{
    /// <summary>
    /// Represents a cube.
    /// </summary>
    public struct Cube
    {
        /// <summary>
        /// Gets the height.
        /// </summary>
        /// <value>The height.</value>
        public int Height
        {
            get { return _height; }
        }
        private int _height;

        /// <summary>
        /// Gets the width.
        /// </summary>
        /// <value>The width.</value>
        public int Width
        {
            get { return _width; }
        }
        private int _width;

        /// <summary>
        /// Gets the depth.
        /// </summary>
        /// <value>The depth.</value>
        public int Depth
        {
            get { return _depth; }
        }
        private int _depth;

        /// <summary>
        /// Gets the volume.
        /// </summary>
        /// <value>The volume.</value>
        public int Volume
        {
            get { return _height * _width * _depth; }
        }

        /// <summary>
        /// Initializes a new instance of the <see cref="T:Cube"/> class.
        /// </summary>
        /// <param name="height">The height.</param>
        /// <param name="width">The width.</param>
        /// <param name="depth">The depth.</param>
        public Cube(int height, int width, int depth)
        {
            if (height < 0)
                throw new ArgumentOutOfRangeException("height");
            if (width < 0)
                throw new ArgumentOutOfRangeException("width");
            if (depth < 0)
                throw new ArgumentOutOfRangeException("depth");
            _height = height;
            _width = width;
            _depth = depth;
        }

        /// <summary>
        /// Returns the fully qualified type name of this instance.
        /// </summary>
        /// <returns>
        /// A <see cref="T:System.String"></see> containing a fully qualified type name.
        /// </returns>
        public override string ToString()
        {
            return _height.ToString() + "; " + _width.ToString() + "; " + _depth.ToString();
        }

        /// <summary>
        /// Returns the hash code for this instance.
        /// </summary>
        /// <returns>
        /// A 32-bit signed integer that is the hash code for this instance.
        /// </returns>
        public override int GetHashCode()
        {
            return this.ToString().GetHashCode();
        }

    }

    /// <summary>
    /// TypeConverter for cube.
    /// </summary>
    public class CubeTypeConverter : TypeConverter
    {
        public override bool CanConvertFrom(ITypeDescriptorContext context, Type sourceType)
        {
            if (sourceType == typeof(string))
                return true;
            return false;
        }

        public override bool CanConvertTo(ITypeDescriptorContext context, Type destinationType)
        {
            if (destinationType == typeof(string))
                return true;
            return false;
        }

        public override object ConvertFrom(ITypeDescriptorContext context, System.Globalization.CultureInfo culture, object value)
        {
            string stringValue = (string)value;
            string[] values = stringValue.Split(',');
            Cube cube = new Cube(int.Parse(values[0]), int.Parse(values[1]), int.Parse(values[1]));
            return cube;
        }

        public override object ConvertTo(ITypeDescriptorContext context, System.Globalization.CultureInfo culture, object value, Type destinationType)
        {
            Cube cube = (Cube)value;
            return cube.ToString();
        }
    }

}
